#pragma once

#include <ostream>
#include "MathUtils.h"

BEGIN_OPT_NAMESPACE

using std::ostream;

const int PointArity = 2;

class OPT_API OptPoint
{
	//double _coord[PointArity];
	double _x;
	double _y;

protected:
	bool isEqualTo(const OptPoint& other)
	{
		return math::equal(x(), other.x()) && math::equal(y(), other.y());
	}

public:
	OptPoint(void);
	OptPoint(double, double);
	virtual ~OptPoint(void);

	inline double x() const { return _x/*_coord[0]*/; }
	inline double y() const { return _y/*_coord[1]*/; }

	OptPoint operator+ (const OptPoint& other)
	{
		return OptPoint(x() + other.x(), y() + other.y());
	}

	OptPoint operator- (const OptPoint& other)
	{
		return OptPoint(x() - other.x(), y() - other.y());
	}

	OptPoint operator* (double d)
	{
		return OptPoint(x() * d, y() * d);
	}

	bool operator== (const OptPoint& o)
	{
		return isEqualTo(o);
	}

	bool operator!= (const OptPoint& o)
	{
		return !isEqualTo(o);
	}

	inline double length() 
	{ 
		return sqrt(math::sqr(x()) + math::sqr(y()));
	}

	OPT_API friend OptPoint operator* (double d, const OptPoint& v);
	OPT_API friend ostream& operator<<(ostream& stream, const OptPoint& v);
};


END_OPT_NAMESPACE